/*
 * 版权所有 (C) 2015 知启蒙(ZHIQIM) 保留所有权利。[遇见知启蒙，邂逅框架梦，本文采用木兰宽松许可证第2版]
 * 
 * https://zhiqim.org/project/zhiqim_products/gitcan.htm
 *
 * gitcan is licensed under Mulan PSL v2.
 * You can use this software according to the terms and conditions of the Mulan PSL v2.
 * You may obtain a copy of Mulan PSL v2 at:
 *          http://license.coscl.org.cn/MulanPSL2
 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
 * See the Mulan PSL v2 for more details.
 */
package org.zhiqim.gitcan.action;

import java.util.ArrayList;
import java.util.List;

import org.zhiqim.gitcan.GitcanConstants;
import org.zhiqim.gitcan.dao.GitCalendarDao;
import org.zhiqim.gitcan.dbo.GitProjectPlan;
import org.zhiqim.gitcan.dbo.GitProjectSummary;
import org.zhiqim.gitcan.model.CalendarWeekModel;
import org.zhiqim.gitcan.model.ProjectModel;
import org.zhiqim.gitcan.model.ProjectPlanModel;
import org.zhiqim.gitcan.model.ProjectWeekModel;
import org.zhiqim.gitsolo.dao.GitProjectDao;
import org.zhiqim.gitsolo.dbo.GitProject;
import org.zhiqim.httpd.HttpRequest;
import org.zhiqim.httpd.context.core.Action;
import org.zhiqim.kernel.util.DateTimes;
import org.zhiqim.kernel.util.Ids;
import org.zhiqim.orm.ORM;
import org.zhiqim.orm.dbo.Selector;

/**
 *  项目计划总结月表 
 *
 * @version v1.0.0 @author zouzhigang 2017-11-2 新建与整理
 */
public class ProjectPlanAction implements Action, GitcanConstants
{
    @Override
    public void execute(HttpRequest request) throws Exception
    {
        long projectId = GitProjectDao.getProjectId(request);
        GitProject project = ORM.table().item(GitProject.class, projectId);
        if(project == null)
        {
            request.returnHistory("请选择一个有效的项目");
            return;
        }
        
        //第一步，从页面中读出当前年月，并根据上下月参数找到对应的年月
        int year = request.getParameterInt("year", DateTimes.getCurrentYear());
        int month = request.getParameterInt("month", DateTimes.getCurrentMonth());
        
        boolean isPrev = request.getParameterBoolean("prev");
        boolean isNext = request.getParameterBoolean("next");
        
        if (isPrev)
        {
            year = month==1?year-1:year;
            month = month==1?12:month-1;
        }
        else if (isNext)
        {
            year = month==12?year+1:year;
            month = month==12?1:month+1;
        }
        
        //第二步，查出上个月，当前月和下个月的个人计划&总结
        int prevYear = month==1?year-1:year;
        int prevMonth = month==1?12:month-1;
        
        int nextYear = month==12?year+1:year;
        int nextMonth = month==12?1:month+1;
        
        Selector selector = new Selector();
        selector.addMust("projectId", projectId);
        selector.addMustThenG("planDate", prevYear * 10000 + prevMonth * 100);
        selector.addMustThenL("planDate", nextYear * 10000 + (nextMonth+1) * 100);
        List<GitProjectPlan> planList = ORM.table().list(GitProjectPlan.class, selector);
        
        Selector selector2 = new Selector();
        selector2.addMust("projectId", projectId);
        selector2.addMustThenG("summaryDate", prevYear * 10000 + prevMonth * 100);
        selector2.addMustThenL("summaryDate", nextYear * 10000 + (nextMonth+1) * 100);
        List<GitProjectSummary> summaryList = ORM.table().list(GitProjectSummary.class, selector2);
        
        //第三步，组装有效周列表
        List<ProjectWeekModel> weekList = new ArrayList<>();
        for (CalendarWeekModel week : GitCalendarDao.getCalendarWeekList(request, year, month))
        {
            weekList.add(new ProjectWeekModel(week));
        }
        
        /******************************************************************************/
        //以下为内容填充
        /******************************************************************************/
        
        //第四步，找到周下面所有的计划
        for (ProjectWeekModel week : weekList)
        {
            CalendarWeekModel key = week.getKey();
            List<GitProjectPlan> pList = getPlan(planList, key.getBeginDate(), key.getEndDate());
            if (pList.isEmpty())
            {//没有计划，则插入一个空项计划
                ProjectPlanModel model = new ProjectPlanModel();
                model.setId(Ids.longId());
                model.setDate(key.getBeginDate());
                model.setPlanSeq(1);
                
                week.addPlanModel(model);
            }
            else
            {//有则用计划表
                for (GitProjectPlan plan : pList)
                {
                    ProjectPlanModel model = new ProjectPlanModel();
                    model.setId(plan.getPlanId());
                    model.setDate(plan.getPlanDate());
                    model.setContent(plan.getPlanContent());
                    
                    model.setPlanSeq(plan.getPlanSeq());
                    model.setPlanStatus(plan.getPlanStatus());
                    model.setPlanBeginDate(plan.getPlanBeginDate());
                    model.setPlanEndDate(plan.getPlanEndDate());
                    model.setActualBeginDate(plan.getActualBeginDate());
                    model.setActualEndDate(plan.getActualEndDate());
                    model.setPlanManager(plan.getPlanManager());
                    model.setPlanProgress(plan.getPlanProgress());
                    
                    week.addPlanModel(model);
                }
            }
        }
        
        //第五步，生成周目标&周总结
        for (ProjectWeekModel week : weekList)
        {
            CalendarWeekModel key = week.getKey();
            
            //周目标
            ProjectModel aModel = new ProjectModel();
            aModel.setType(PJ_WEEK_AIM);
            aModel.setDate(key.getBeginDate());
            
            GitProjectSummary summary = getWeekAim(summaryList, key.getBeginDate(), key.getEndDate());
            if (summary != null)
            {
                aModel.setId(summary.getSummaryId());
                aModel.setContent(summary.getSummaryContent());
            }
            
            week.setWeekAim(aModel);
            
            //周总结
            ProjectModel sModel = new ProjectModel();
            sModel.setType(PJ_WEEK_SUM);
            sModel.setDate(key.getBeginDate());
            
            summary = getWeekSummary(summaryList, key.getBeginDate(), key.getEndDate());
            if (summary != null)
            {
                sModel.setId(summary.getSummaryId());
                sModel.setContent(summary.getSummaryContent());
            }
            
            week.setWeekSummary(sModel);
        }
        
        //第六步，生成月总结
        int monthDate = year * 10000 + month * 100 + 1;
        
        ProjectModel monthModel = new ProjectModel();
        monthModel.setType(PJ_MONTH_SUM);
        monthModel.setDate(monthDate);
        
        GitProjectSummary summary = getProjectSummary(summaryList, monthDate, PJ_MONTH_SUM);
        if (summary != null)
        {
            monthModel.setId(summary.getSummaryId());
            monthModel.setContent(summary.getSummaryContent());
        }
        
        request.setAttribute("project", project);
        request.setAttribute("year", year);
        request.setAttribute("month", month);
        request.setAttribute("weekList", weekList);
        request.setAttribute("monthModel", monthModel);
    }
    
    /*********************************************************************************************************/
    //内部实现方法
    /*********************************************************************************************************/
    
    /** 找出本周的计划 */
    private static List<GitProjectPlan> getPlan(List<GitProjectPlan> planList, int beginDate, int endDate)
    {
        List<GitProjectPlan> pList = new ArrayList<>();
        for (GitProjectPlan item : planList)
        {
            if (item.getPlanDate() < beginDate || item.getPlanDate() > endDate)
                continue;
            
            pList.add(item);
        }
        
        return pList;
    }
    
    /** 找出本周的目标 */
    private static GitProjectSummary getWeekAim(List<GitProjectSummary> planList, int beginDate, int endDate)
    {
        for (GitProjectSummary item : planList)
        {
            if (item.getSummaryType() != PJ_WEEK_AIM)
                continue;
            
            if (item.getSummaryDate() < beginDate || item.getSummaryDate() > endDate)
                continue;
            
            return item;
        }
        
        return null;
    }
    
    /** 找出本周的总结 */
    private static GitProjectSummary getWeekSummary(List<GitProjectSummary> planList, int beginDate, int endDate)
    {
        for (GitProjectSummary item : planList)
        {
            if (item.getSummaryType() != PJ_WEEK_SUM)
                continue;
            
            if (item.getSummaryDate() < beginDate || item.getSummaryDate() > endDate)
                continue;
            
            return item;
        }
        
        return null;
    }
    
    /** 找出类型和日期对应的总结 */
    private static GitProjectSummary getProjectSummary(List<GitProjectSummary> summaryList, int date, int type)
    {
        for (GitProjectSummary item : summaryList)
        {
            if (item.getSummaryDate() == date && item.getSummaryType() == type)
                return item;
        }
        
        return null;
    }
}
